home *** CD-ROM | disk | FTP | other *** search
/ PC/CD Gamer UK 120 / CD Gamer Issue 120 (March 2003) (Disc 2).ISO / mods / Q2_Codered / codeRED1_0.exe / Data1.cab / g_items.c < prev    next >
Encoding:
C/C++ Source or Header  |  2002-08-13  |  51.5 KB  |  2,447 lines

  1. /*
  2. Copyright (C) 1997-2001 Id Software, Inc.
  3.  
  4. This program is free software; you can redistribute it and/or
  5. modify it under the terms of the GNU General Public License
  6. as published by the Free Software Foundation; either version 2
  7. of the License, or (at your option) any later version.
  8.  
  9. This program is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  
  12.  
  13. See the GNU General Public License for more details.
  14.  
  15. You should have received a copy of the GNU General Public License
  16. along with this program; if not, write to the Free Software
  17. Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
  18.  
  19. */
  20. #include "g_local.h"
  21.  
  22.  
  23. qboolean    Pickup_Weapon (edict_t *ent, edict_t *other);
  24. void        Use_Weapon (edict_t *ent, gitem_t *inv);
  25. void        Drop_Weapon (edict_t *ent, gitem_t *inv);
  26.  
  27. void Weapon_Blaster (edict_t *ent);
  28. void Weapon_Shotgun (edict_t *ent);
  29. void Weapon_SuperShotgun (edict_t *ent);
  30. void Weapon_Machinegun (edict_t *ent);
  31. void Weapon_Chaingun (edict_t *ent);
  32. void Weapon_HyperBlaster (edict_t *ent);
  33. void Weapon_RocketLauncher (edict_t *ent);
  34. void Weapon_Grenade (edict_t *ent);
  35. void Weapon_GrenadeLauncher (edict_t *ent);
  36. void Weapon_Railgun (edict_t *ent);
  37. void Weapon_BFG (edict_t *ent);
  38.  
  39. gitem_armor_t jacketarmor_info    = { 25,  50, .30, .00, ARMOR_JACKET};
  40. gitem_armor_t combatarmor_info    = { 50, 100, .60, .30, ARMOR_COMBAT};
  41. gitem_armor_t bodyarmor_info    = {100, 200, .80, .60, ARMOR_BODY};
  42.  
  43. static int    jacket_armor_index;
  44. static int    combat_armor_index;
  45. static int    body_armor_index;
  46. static int    power_screen_index;
  47. static int    power_shield_index;
  48.  
  49. #define HEALTH_IGNORE_MAX    1
  50. #define HEALTH_TIMED        2
  51.  
  52. void Use_Quad (edict_t *ent, gitem_t *item);
  53. static int    quad_drop_timeout_hack;
  54.  
  55. //======================================================================
  56.  
  57. /*
  58. ===============
  59. GetItemByIndex
  60. ===============
  61. */
  62. gitem_t    *GetItemByIndex (int index)
  63. {
  64.     if (index == 0 || index >= game.num_items)
  65.         return NULL;
  66.  
  67.     return &itemlist[index];
  68. }
  69.  
  70.  
  71. /*
  72. ===============
  73. FindItemByClassname
  74.  
  75. ===============
  76. */
  77. gitem_t    *FindItemByClassname (char *classname)
  78. {
  79.     int        i;
  80.     gitem_t    *it;
  81.  
  82.     it = itemlist;
  83.     for (i=0 ; i<game.num_items ; i++, it++)
  84.     {
  85.         if (!it->classname)
  86.             continue;
  87.         if (!Q_stricmp(it->classname, classname))
  88.             return it;
  89.     }
  90.  
  91.     return NULL;
  92. }
  93.  
  94. /*
  95. ===============
  96. FindItem
  97.  
  98. ===============
  99. */
  100. gitem_t    *FindItem (char *pickup_name)
  101. {
  102.     int        i;
  103.     gitem_t    *it;
  104.  
  105.     it = itemlist;
  106.     for (i=0 ; i<game.num_items ; i++, it++)
  107.     {
  108.         if (!it->pickup_name)
  109.             continue;
  110.         if (!Q_stricmp(it->pickup_name, pickup_name))
  111.             return it;
  112.     }
  113.  
  114.     return NULL;
  115. }
  116.  
  117. //======================================================================
  118.  
  119. void DoRespawn (edict_t *ent)
  120. {
  121.     if (ent->team)
  122.     {
  123.         edict_t    *master;
  124.         int    count;
  125.         int choice;
  126.  
  127.         master = ent->teammaster;
  128.  
  129. //ZOID
  130. //in ctf, when we are weapons stay, only the master of a team of weapons
  131. //is spawned
  132.         if (ctf->value &&
  133.             ((int)dmflags->value & DF_WEAPONS_STAY) &&
  134.             master->item && (master->item->flags & IT_WEAPON))
  135.             ent = master;
  136.         else {
  137. //ZOID
  138.  
  139.             for (count = 0, ent = master; ent; ent = ent->chain, count++)
  140.                 ;
  141.  
  142.             choice = rand() % count;
  143.  
  144.             for (count = 0, ent = master; count < choice; ent = ent->chain, count++)
  145.                 ;
  146.         }
  147.     }
  148.  
  149.     ent->svflags &= ~SVF_NOCLIENT;
  150.     ent->solid = SOLID_TRIGGER;
  151.     gi.linkentity (ent);
  152.  
  153.     // send an effect
  154.     ent->s.event = EV_ITEM_RESPAWN;
  155. }
  156.  
  157. void SetRespawn (edict_t *ent, float delay)
  158. {
  159.     ent->flags |= FL_RESPAWN;
  160.     ent->svflags |= SVF_NOCLIENT;
  161.     ent->solid = SOLID_NOT;
  162.     ent->nextthink = level.time + delay;
  163.     ent->think = DoRespawn;
  164.     gi.linkentity (ent);
  165. }
  166.  
  167.  
  168. //======================================================================
  169.  
  170. qboolean Pickup_Powerup (edict_t *ent, edict_t *other)
  171. {
  172.     int        quantity;
  173.  
  174.     quantity = other->client->pers.inventory[ITEM_INDEX(ent->item)];
  175.     if ((skill->value == 1 && quantity >= 2) || (skill->value >= 2 && quantity >= 1))
  176.         return false;
  177.  
  178.     if ((coop->value) && (ent->item->flags & IT_STAY_COOP) && (quantity > 0))
  179.         return false;
  180.  
  181.     other->client->pers.inventory[ITEM_INDEX(ent->item)]++;
  182.  
  183.     if (deathmatch->value)
  184.     {
  185.         if (!(ent->spawnflags & DROPPED_ITEM) )
  186.             SetRespawn (ent, ent->item->quantity);
  187.         if (((int)dmflags->value & DF_INSTANT_ITEMS) || ((ent->item->use == Use_Quad) && (ent->spawnflags & DROPPED_PLAYER_ITEM)))
  188.         {
  189.             if ((ent->item->use == Use_Quad) && (ent->spawnflags & DROPPED_PLAYER_ITEM))
  190.                 quad_drop_timeout_hack = (ent->nextthink - level.time) / FRAMETIME;
  191.             ent->item->use (other, ent->item);
  192.         }
  193.     }
  194.  
  195.     return true;
  196. }
  197.  
  198. void Drop_General (edict_t *ent, gitem_t *item)
  199. {
  200.     Drop_Item (ent, item);
  201.     ent->client->pers.inventory[ITEM_INDEX(item)]--;
  202.     ValidateSelectedItem (ent);
  203. }
  204.  
  205.  
  206. //======================================================================
  207.  
  208. qboolean Pickup_Adrenaline (edict_t *ent, edict_t *other)
  209. {
  210.     if (!deathmatch->value)
  211.         other->max_health += 1;
  212.  
  213.     if (other->health < other->max_health)
  214.         other->health = other->max_health;
  215.  
  216.     if (!(ent->spawnflags & DROPPED_ITEM) && (deathmatch->value))
  217.         SetRespawn (ent, ent->item->quantity);
  218.  
  219.     return true;
  220. }
  221.  
  222. qboolean Pickup_AncientHead (edict_t *ent, edict_t *other)
  223. {
  224.     other->max_health += 2;
  225.  
  226.     if (!(ent->spawnflags & DROPPED_ITEM) && (deathmatch->value))
  227.         SetRespawn (ent, ent->item->quantity);
  228.  
  229.     return true;
  230. }
  231.  
  232. qboolean Pickup_Bandolier (edict_t *ent, edict_t *other)
  233. {
  234.     gitem_t    *item;
  235.     int        index;
  236.  
  237.     if (other->client->pers.max_bullets < 250)
  238.         other->client->pers.max_bullets = 250;
  239.     if (other->client->pers.max_shells < 150)
  240.         other->client->pers.max_shells = 150;
  241.     if (other->client->pers.max_cells < 250)
  242.         other->client->pers.max_cells = 250;
  243.     if (other->client->pers.max_slugs < 75)
  244.         other->client->pers.max_slugs = 75;
  245.  
  246.     item = FindItem("Bullets");
  247.     if (item)
  248.     {
  249.         index = ITEM_INDEX(item);
  250.         other->client->pers.inventory[index] += item->quantity;
  251.         if (other->client->pers.inventory[index] > other->client->pers.max_bullets)
  252.             other->client->pers.inventory[index] = other->client->pers.max_bullets;
  253.     }
  254.  
  255.     item = FindItem("Shells");
  256.     if (item)
  257.     {
  258.         index = ITEM_INDEX(item);
  259.         other->client->pers.inventory[index] += item->quantity;
  260.         if (other->client->pers.inventory[index] > other->client->pers.max_shells)
  261.             other->client->pers.inventory[index] = other->client->pers.max_shells;
  262.     }
  263.  
  264.     if (!(ent->spawnflags & DROPPED_ITEM) && (deathmatch->value))
  265.         SetRespawn (ent, ent->item->quantity);
  266.  
  267.     return true;
  268. }
  269.  
  270. qboolean Pickup_Pack (edict_t *ent, edict_t *other)
  271. {
  272.     gitem_t    *item;
  273.     int        index;
  274.  
  275.     if (other->client->pers.max_bullets < 300)
  276.         other->client->pers.max_bullets = 300;
  277.     if (other->client->pers.max_shells < 200)
  278.         other->client->pers.max_shells = 200;
  279.     if (other->client->pers.max_rockets < 100)
  280.         other->client->pers.max_rockets = 100;
  281.     if (other->client->pers.max_grenades < 100)
  282.         other->client->pers.max_grenades = 100;
  283.     if (other->client->pers.max_cells < 300)
  284.         other->client->pers.max_cells = 300;
  285.     if (other->client->pers.max_slugs < 100)
  286.         other->client->pers.max_slugs = 100;
  287.  
  288.     item = FindItem("Bullets");
  289.     if (item)
  290.     {
  291.         index = ITEM_INDEX(item);
  292.         other->client->pers.inventory[index] += item->quantity;
  293.         if (other->client->pers.inventory[index] > other->client->pers.max_bullets)
  294.             other->client->pers.inventory[index] = other->client->pers.max_bullets;
  295.     }
  296.  
  297.     item = FindItem("Shells");
  298.     if (item)
  299.     {
  300.         index = ITEM_INDEX(item);
  301.         other->client->pers.inventory[index] += item->quantity;
  302.         if (other->client->pers.inventory[index] > other->client->pers.max_shells)
  303.             other->client->pers.inventory[index] = other->client->pers.max_shells;
  304.     }
  305.  
  306.     item = FindItem("Cells");
  307.     if (item)
  308.     {
  309.         index = ITEM_INDEX(item);
  310.         other->client->pers.inventory[index] += item->quantity;
  311.         if (other->client->pers.inventory[index] > other->client->pers.max_cells)
  312.             other->client->pers.inventory[index] = other->client->pers.max_cells;
  313.     }
  314.  
  315.     item = FindItem("Grenades");
  316.     if (item)
  317.     {
  318.         index = ITEM_INDEX(item);
  319.         other->client->pers.inventory[index] += item->quantity;
  320.         if (other->client->pers.inventory[index] > other->client->pers.max_grenades)
  321.             other->client->pers.inventory[index] = other->client->pers.max_grenades;
  322.     }
  323.  
  324.     item = FindItem("Rockets");
  325.     if (item)
  326.     {
  327.         index = ITEM_INDEX(item);
  328.         other->client->pers.inventory[index] += item->quantity;
  329.         if (other->client->pers.inventory[index] > other->client->pers.max_rockets)
  330.             other->client->pers.inventory[index] = other->client->pers.max_rockets;
  331.     }
  332.  
  333.     item = FindItem("Slugs");
  334.     if (item)
  335.     {
  336.         index = ITEM_INDEX(item);
  337.         other->client->pers.inventory[index] += item->quantity;
  338.         if (other->client->pers.inventory[index] > other->client->pers.max_slugs)
  339.             other->client->pers.inventory[index] = other->client->pers.max_slugs;
  340.     }
  341.  
  342.     if (!(ent->spawnflags & DROPPED_ITEM) && (deathmatch->value))
  343.         SetRespawn (ent, ent->item->quantity);
  344.  
  345.     return true;
  346. }
  347.  
  348. //======================================================================
  349.  
  350. void Use_Quad (edict_t *ent, gitem_t *item)
  351. {
  352.     int        timeout;
  353.  
  354.     ent->client->pers.inventory[ITEM_INDEX(item)]--;
  355.     ValidateSelectedItem (ent);
  356.  
  357.     if (quad_drop_timeout_hack)
  358.     {
  359.         timeout = quad_drop_timeout_hack;
  360.         quad_drop_timeout_hack = 0;
  361.     }
  362.     else
  363.     {
  364.         timeout = 300;
  365.     }
  366.  
  367.     if (ent->client->quad_framenum > level.framenum)
  368.         ent->client->quad_framenum += timeout;
  369.     else
  370.         ent->client->quad_framenum = level.framenum + timeout;
  371.  
  372.     gi.sound(ent, CHAN_ITEM, gi.soundindex("items/damage.wav"), 1, ATTN_NORM, 0);
  373. }
  374.  
  375. //======================================================================
  376.  
  377. void Use_Breather (edict_t *ent, gitem_t *item)
  378. {
  379.     ent->client->pers.inventory[ITEM_INDEX(item)]--;
  380.     ValidateSelectedItem (ent);
  381.  
  382.     if (ent->client->breather_framenum > level.framenum)
  383.         ent->client->breather_framenum += 300;
  384.     else
  385.         ent->client->breather_framenum = level.framenum + 300;
  386.  
  387. //    gi.sound(ent, CHAN_ITEM, gi.soundindex("items/damage.wav"), 1, ATTN_NORM, 0);
  388. }
  389.  
  390. //======================================================================
  391.  
  392. void Use_Envirosuit (edict_t *ent, gitem_t *item)
  393. {
  394.     ent->client->pers.inventory[ITEM_INDEX(item)]--;
  395.     ValidateSelectedItem (ent);
  396.  
  397.     if (ent->client->enviro_framenum > level.framenum)
  398.         ent->client->enviro_framenum += 300;
  399.     else
  400.         ent->client->enviro_framenum = level.framenum + 300;
  401.  
  402. //    gi.sound(ent, CHAN_ITEM, gi.soundindex("items/damage.wav"), 1, ATTN_NORM, 0);
  403. }
  404.  
  405. //======================================================================
  406.  
  407. void    Use_Invulnerability (edict_t *ent, gitem_t *item)
  408. {
  409.     ent->client->pers.inventory[ITEM_INDEX(item)]--;
  410.     ValidateSelectedItem (ent);
  411.  
  412.     if (ent->client->invincible_framenum > level.framenum)
  413.         ent->client->invincible_framenum += 300;
  414.     else
  415.         ent->client->invincible_framenum = level.framenum + 300;
  416.  
  417.     gi.sound(ent, CHAN_ITEM, gi.soundindex("items/protect.wav"), 1, ATTN_NORM, 0);
  418. }
  419.  
  420. //======================================================================
  421.  
  422. void    Use_Silencer (edict_t *ent, gitem_t *item)
  423. {
  424.     ent->client->pers.inventory[ITEM_INDEX(item)]--;
  425.     ValidateSelectedItem (ent);
  426.     ent->client->silencer_shots += 30;
  427.  
  428. //    gi.sound(ent, CHAN_ITEM, gi.soundindex("items/damage.wav"), 1, ATTN_NORM, 0);
  429. }
  430.  
  431. //======================================================================
  432.  
  433. qboolean Pickup_Key (edict_t *ent, edict_t *other)
  434. {
  435.     if (coop->value)
  436.     {
  437.         if (strcmp(ent->classname, "key_power_cube") == 0)
  438.         {
  439.             if (other->client->pers.power_cubes & ((ent->spawnflags & 0x0000ff00)>> 8))
  440.                 return false;
  441.             other->client->pers.inventory[ITEM_INDEX(ent->item)]++;
  442.             other->client->pers.power_cubes |= ((ent->spawnflags & 0x0000ff00) >> 8);
  443.         }
  444.         else
  445.         {
  446.             if (other->client->pers.inventory[ITEM_INDEX(ent->item)])
  447.                 return false;
  448.             other->client->pers.inventory[ITEM_INDEX(ent->item)] = 1;
  449.         }
  450.         return true;
  451.     }
  452.     other->client->pers.inventory[ITEM_INDEX(ent->item)]++;
  453.     return true;
  454. }
  455.  
  456. //======================================================================
  457.  
  458. qboolean Add_Ammo (edict_t *ent, gitem_t *item, int count)
  459. {
  460.     int            index;
  461.     int            max;
  462.  
  463.     if (!ent->client)
  464.         return false;
  465.  
  466.     if (item->tag == AMMO_BULLETS)
  467.         max = ent->client->pers.max_bullets;
  468.     else if (item->tag == AMMO_SHELLS)
  469.         max = ent->client->pers.max_shells;
  470.     else if (item->tag == AMMO_ROCKETS)
  471.         max = ent->client->pers.max_rockets;
  472.     else if (item->tag == AMMO_GRENADES)
  473.         max = ent->client->pers.max_grenades;
  474.     else if (item->tag == AMMO_CELLS)
  475.         max = ent->client->pers.max_cells;
  476.     else if (item->tag == AMMO_SLUGS)
  477.         max = ent->client->pers.max_slugs;
  478.     else
  479.         return false;
  480.  
  481.     index = ITEM_INDEX(item);
  482.  
  483.     if (ent->client->pers.inventory[index] == max)
  484.         return false;
  485.  
  486.     ent->client->pers.inventory[index] += count;
  487.  
  488.     if (ent->client->pers.inventory[index] > max)
  489.         ent->client->pers.inventory[index] = max;
  490.  
  491.     return true;
  492. }
  493.  
  494. qboolean Pickup_Ammo (edict_t *ent, edict_t *other)
  495. {
  496.     int            oldcount;
  497.     int            count;
  498.     qboolean    weapon;
  499.  
  500.     weapon = (ent->item->flags & IT_WEAPON);
  501.     if ( (weapon) && ( (int)dmflags->value & DF_INFINITE_AMMO ) )
  502.         count = 1000;
  503.     else if (ent->count)
  504.         count = ent->count;
  505.     else
  506.         count = ent->item->quantity;
  507.  
  508.     oldcount = other->client->pers.inventory[ITEM_INDEX(ent->item)];
  509.  
  510.     if (!Add_Ammo (other, ent->item, count))
  511.         return false;
  512.  
  513.     if (weapon && !oldcount)
  514.     {
  515.         if (other->client->pers.weapon != ent->item && ( !deathmatch->value || other->client->pers.weapon == FindItem("blaster") ) )
  516.             other->client->newweapon = ent->item;
  517.     }
  518.  
  519.     if (!(ent->spawnflags & (DROPPED_ITEM | DROPPED_PLAYER_ITEM)) && (deathmatch->value))
  520.         SetRespawn (ent, 30);
  521.     return true;
  522. }
  523.  
  524. void Drop_Ammo (edict_t *ent, gitem_t *item)
  525. {
  526.     edict_t    *dropped;
  527.     int        index;
  528.  
  529.     index = ITEM_INDEX(item);
  530.     dropped = Drop_Item (ent, item);
  531.     if (ent->client->pers.inventory[index] >= item->quantity)
  532.         dropped->count = item->quantity;
  533.     else
  534.         dropped->count = ent->client->pers.inventory[index];
  535.     ent->client->pers.inventory[index] -= dropped->count;
  536.     ValidateSelectedItem (ent);
  537. }
  538.  
  539.  
  540. //======================================================================
  541.  
  542. void MegaHealth_think (edict_t *self)
  543. {
  544.     if (self->owner->health > self->owner->max_health
  545. //ZOID
  546.         && !CTFHasRegeneration(self->owner)
  547. //ZOID
  548.         )
  549.     {
  550.         self->nextthink = level.time + 1;
  551.         self->owner->health -= 1;
  552.         return;
  553.     }
  554.  
  555.     if (!(self->spawnflags & DROPPED_ITEM) && (deathmatch->value))
  556.         SetRespawn (self, 20);
  557.     else
  558.         G_FreeEdict (self);
  559. }
  560.  
  561. qboolean Pickup_Health (edict_t *ent, edict_t *other)
  562. {
  563.     if (!(ent->style & HEALTH_IGNORE_MAX))
  564.         if (other->health >= other->max_health)
  565.             return false;
  566.  
  567. //ZOID
  568.     if (other->health >= 250 && ent->count > 25)
  569.         return false;
  570. //ZOID
  571.  
  572.     other->health += ent->count;
  573.  
  574. //ZOID
  575.     if (other->health > 250 && ent->count > 25)
  576.         other->health = 250;
  577. //ZOID
  578.  
  579.     if (!(ent->style & HEALTH_IGNORE_MAX))
  580.     {
  581.         if (other->health > other->max_health)
  582.             other->health = other->max_health;
  583.     }
  584.  
  585. //ZOID
  586.     if ((ent->style & HEALTH_TIMED)
  587.         && !CTFHasRegeneration(other)
  588. //ZOID
  589.     )
  590.     {
  591.         ent->think = MegaHealth_think;
  592.         ent->nextthink = level.time + 5;
  593.         ent->owner = other;
  594.         ent->flags |= FL_RESPAWN;
  595.         ent->svflags |= SVF_NOCLIENT;
  596.         ent->solid = SOLID_NOT;
  597.     }
  598.     else
  599.     {
  600.         if (!(ent->spawnflags & DROPPED_ITEM) && (deathmatch->value))
  601.             SetRespawn (ent, 30);
  602.     }
  603.  
  604.     return true;
  605. }
  606.  
  607. //======================================================================
  608.  
  609. int ArmorIndex (edict_t *ent)
  610. {
  611.     if (!ent->client)
  612.         return 0;
  613.  
  614.     if (ent->client->pers.inventory[jacket_armor_index] > 0)
  615.         return jacket_armor_index;
  616.  
  617.     if (ent->client->pers.inventory[combat_armor_index] > 0)
  618.         return combat_armor_index;
  619.  
  620.     if (ent->client->pers.inventory[body_armor_index] > 0)
  621.         return body_armor_index;
  622.  
  623.     return 0;
  624. }
  625.  
  626. qboolean Pickup_Armor (edict_t *ent, edict_t *other)
  627. {
  628.     int                old_armor_index;
  629.     gitem_armor_t    *oldinfo;
  630.     gitem_armor_t    *newinfo;
  631.     int                newcount;
  632.     float            salvage;
  633.     int                salvagecount;
  634.  
  635.     // get info on new armor
  636.     newinfo = (gitem_armor_t *)ent->item->info;
  637.  
  638.     old_armor_index = ArmorIndex (other);
  639.  
  640.     // handle armor shards specially
  641.     if (ent->item->tag == ARMOR_SHARD)
  642.     {
  643.         if (!old_armor_index)
  644.             other->client->pers.inventory[jacket_armor_index] = 2;
  645.         else
  646.             other->client->pers.inventory[old_armor_index] += 2;
  647.     }
  648.  
  649.     // if player has no armor, just use it
  650.     else if (!old_armor_index)
  651.     {
  652.         other->client->pers.inventory[ITEM_INDEX(ent->item)] = newinfo->base_count;
  653.     }
  654.  
  655.     // use the better armor
  656.     else
  657.     {
  658.         // get info on old armor
  659.         if (old_armor_index == jacket_armor_index)
  660.             oldinfo = &jacketarmor_info;
  661.         else if (old_armor_index == combat_armor_index)
  662.             oldinfo = &combatarmor_info;
  663.         else // (old_armor_index == body_armor_index)
  664.             oldinfo = &bodyarmor_info;
  665.  
  666.         if (newinfo->normal_protection > oldinfo->normal_protection)
  667.         {
  668.             // calc new armor values
  669.             salvage = oldinfo->normal_protection / newinfo->normal_protection;
  670.             salvagecount = salvage * other->client->pers.inventory[old_armor_index];
  671.             newcount = newinfo->base_count + salvagecount;
  672.             if (newcount > newinfo->max_count)
  673.                 newcount = newinfo->max_count;
  674.  
  675.             // zero count of old armor so it goes away
  676.             other->client->pers.inventory[old_armor_index] = 0;
  677.  
  678.             // change armor to new item with computed value
  679.             other->client->pers.inventory[ITEM_INDEX(ent->item)] = newcount;
  680.         }
  681.         else
  682.         {
  683.             // calc new armor values
  684.             salvage = newinfo->normal_protection / oldinfo->normal_protection;
  685.             salvagecount = salvage * newinfo->base_count;
  686.             newcount = other->client->pers.inventory[old_armor_index] + salvagecount;
  687.             if (newcount > oldinfo->max_count)
  688.                 newcount = oldinfo->max_count;
  689.  
  690.             // if we're already maxed out then we don't need the new armor
  691.             if (other->client->pers.inventory[old_armor_index] >= newcount)
  692.                 return false;
  693.  
  694.             // update current armor value
  695.             other->client->pers.inventory[old_armor_index] = newcount;
  696.         }
  697.     }
  698.  
  699.     if (!(ent->spawnflags & DROPPED_ITEM) && (deathmatch->value))
  700.         SetRespawn (ent, 20);
  701.  
  702.     return true;
  703. }
  704.  
  705. //======================================================================
  706.  
  707. int PowerArmorType (edict_t *ent)
  708. {
  709.     if (!ent->client)
  710.         return POWER_ARMOR_NONE;
  711.  
  712.     if (!(ent->flags & FL_POWER_ARMOR))
  713.         return POWER_ARMOR_NONE;
  714.  
  715.     if (ent->client->pers.inventory[power_shield_index] > 0)
  716.         return POWER_ARMOR_SHIELD;
  717.  
  718.     if (ent->client->pers.inventory[power_screen_index] > 0)
  719.         return POWER_ARMOR_SCREEN;
  720.  
  721.     return POWER_ARMOR_NONE;
  722. }
  723.  
  724. void Use_PowerArmor (edict_t *ent, gitem_t *item)
  725. {
  726.     int        index;
  727.  
  728.     if (ent->flags & FL_POWER_ARMOR)
  729.     {
  730.         ent->flags &= ~FL_POWER_ARMOR;
  731.         gi.sound(ent, CHAN_AUTO, gi.soundindex("misc/power2.wav"), 1, ATTN_NORM, 0);
  732.     }
  733.     else
  734.     {
  735.         index = ITEM_INDEX(FindItem("cells"));
  736.         if (!ent->client->pers.inventory[index])
  737.         {
  738.             gi.cprintf (ent, PRINT_HIGH, "No cells for power armor.\n");
  739.             return;
  740.         }
  741.         ent->flags |= FL_POWER_ARMOR;
  742.         gi.sound(ent, CHAN_AUTO, gi.soundindex("misc/power1.wav"), 1, ATTN_NORM, 0);
  743.     }
  744. }
  745.  
  746. qboolean Pickup_PowerArmor (edict_t *ent, edict_t *other)
  747. {
  748.     int        quantity;
  749.  
  750.     quantity = other->client->pers.inventory[ITEM_INDEX(ent->item)];
  751.  
  752.     other->client->pers.inventory[ITEM_INDEX(ent->item)]++;
  753.  
  754.     if (deathmatch->value)
  755.     {
  756.         if (!(ent->spawnflags & DROPPED_ITEM) )
  757.             SetRespawn (ent, ent->item->quantity);
  758.         // auto-use for DM only if we didn't already have one
  759.         if (!quantity)
  760.             ent->item->use (other, ent->item);
  761.     }
  762.  
  763.     return true;
  764. }
  765.  
  766. void Drop_PowerArmor (edict_t *ent, gitem_t *item)
  767. {
  768.     if ((ent->flags & FL_POWER_ARMOR) && (ent->client->pers.inventory[ITEM_INDEX(item)] == 1))
  769.         Use_PowerArmor (ent, item);
  770.     Drop_General (ent, item);
  771. }
  772.  
  773. //======================================================================
  774.  
  775. /*
  776. ===============
  777. Touch_Item
  778. ===============
  779. */
  780. void Touch_Item (edict_t *ent, edict_t *other, cplane_t *plane, csurface_t *surf)
  781. {
  782.     qboolean    taken;
  783.  
  784.     if (!other->client)
  785.         return;
  786.     if (other->health < 1)
  787.         return;        // dead people can't pickup
  788.     if (!ent->item->pickup)
  789.         return;        // not a grabbable item?
  790.  
  791.     if (CTFMatchSetup())
  792.         return; // can't pick stuff up right now
  793.  
  794.     taken = ent->item->pickup(ent, other);
  795.  
  796.     if (taken)
  797.     {
  798.         // flash the screen
  799.         other->client->bonus_alpha = 0.25;    
  800.  
  801.         // show icon and name on status bar
  802.         other->client->ps.stats[STAT_PICKUP_ICON] = gi.imageindex(ent->item->icon);
  803.         other->client->ps.stats[STAT_PICKUP_STRING] = CS_ITEMS+ITEM_INDEX(ent->item);
  804.         other->client->pickup_msg_time = level.time + 3.0;
  805.  
  806.         // change selected item
  807.         if (ent->item->use)
  808.             other->client->pers.selected_item = other->client->ps.stats[STAT_SELECTED_ITEM] = ITEM_INDEX(ent->item);
  809.  
  810.         if (ent->item->pickup == Pickup_Health)
  811.         {
  812.             if (ent->count == 2)
  813.                 gi.sound(other, CHAN_ITEM, gi.soundindex("items/s_health.wav"), 1, ATTN_NORM, 0);
  814.             else if (ent->count == 10)
  815.                 gi.sound(other, CHAN_ITEM, gi.soundindex("items/n_health.wav"), 1, ATTN_NORM, 0);
  816.             else if (ent->count == 25)
  817.                 gi.sound(other, CHAN_ITEM, gi.soundindex("items/l_health.wav"), 1, ATTN_NORM, 0);
  818.             else // (ent->count == 100)
  819.                 gi.sound(other, CHAN_ITEM, gi.soundindex("items/m_health.wav"), 1, ATTN_NORM, 0);
  820.         }
  821.         else if (ent->item->pickup_sound)
  822.         {
  823.             gi.sound(other, CHAN_ITEM, gi.soundindex(ent->item->pickup_sound), 1, ATTN_NORM, 0);
  824.         }
  825.     }
  826.  
  827.     if (!(ent->spawnflags & ITEM_TARGETS_USED))
  828.     {
  829.         G_UseTargets (ent, other);
  830.         ent->spawnflags |= ITEM_TARGETS_USED;
  831.     }
  832.  
  833.     if (!taken)
  834.         return;
  835.  
  836.     if (!((coop->value) &&  (ent->item->flags & IT_STAY_COOP)) || (ent->spawnflags & (DROPPED_ITEM | DROPPED_PLAYER_ITEM)))
  837.     {
  838.         if (ent->flags & FL_RESPAWN)
  839.             ent->flags &= ~FL_RESPAWN;
  840.         else
  841.             G_FreeEdict (ent);
  842.     }
  843. }
  844.  
  845. //======================================================================
  846.  
  847. static void drop_temp_touch (edict_t *ent, edict_t *other, cplane_t *plane, csurface_t *surf)
  848. {
  849.     if (other == ent->owner)
  850.         return;
  851.  
  852.     Touch_Item (ent, other, plane, surf);
  853. }
  854.  
  855. static void drop_make_touchable (edict_t *ent)
  856. {
  857.     ent->touch = Touch_Item;
  858.     if (deathmatch->value)
  859.     {
  860.         ent->nextthink = level.time + 29;
  861.         ent->think = G_FreeEdict;
  862.     }
  863. }
  864.  
  865. edict_t *Drop_Item (edict_t *ent, gitem_t *item)
  866. {
  867.     edict_t    *dropped;
  868.     vec3_t    forward, right;
  869.     vec3_t    offset;
  870.  
  871.     dropped = G_Spawn();
  872.  
  873.     dropped->classname = item->classname;
  874.     dropped->item = item;
  875.     dropped->spawnflags = DROPPED_ITEM;
  876.     dropped->s.effects = item->world_model_flags;
  877.     dropped->s.renderfx = RF_GLOW;
  878.     VectorSet (dropped->mins, -15, -15, -15);
  879.     VectorSet (dropped->maxs, 15, 15, 15);
  880.     gi.setmodel (dropped, dropped->item->world_model);
  881.     dropped->solid = SOLID_TRIGGER;
  882.     dropped->movetype = MOVETYPE_TOSS;  
  883.     dropped->touch = drop_temp_touch;
  884.     dropped->owner = ent;
  885.  
  886.     if (ent->client)
  887.     {
  888.         trace_t    trace;
  889.  
  890.         AngleVectors (ent->client->v_angle, forward, right, NULL);
  891.         VectorSet(offset, 24, 0, -16);
  892.         G_ProjectSource (ent->s.origin, offset, forward, right, dropped->s.origin);
  893.         trace = gi.trace (ent->s.origin, dropped->mins, dropped->maxs,
  894.             dropped->s.origin, ent, CONTENTS_SOLID);
  895.         VectorCopy (trace.endpos, dropped->s.origin);
  896.     }
  897.     else
  898.     {
  899.         AngleVectors (ent->s.angles, forward, right, NULL);
  900.         VectorCopy (ent->s.origin, dropped->s.origin);
  901.     }
  902.  
  903.     VectorScale (forward, 100, dropped->velocity);
  904.     dropped->velocity[2] = 300;
  905.  
  906.     dropped->think = drop_make_touchable;
  907.     dropped->nextthink = level.time + 1;
  908.  
  909.     gi.linkentity (dropped);
  910.  
  911.     return dropped;
  912. }
  913.  
  914. void Use_Item (edict_t *ent, edict_t *other, edict_t *activator)
  915. {
  916.     ent->svflags &= ~SVF_NOCLIENT;
  917.     ent->use = NULL;
  918.  
  919.     if (ent->spawnflags & ITEM_NO_TOUCH)
  920.     {
  921.         ent->solid = SOLID_BBOX;
  922.         ent->touch = NULL;
  923.     }
  924.     else
  925.     {
  926.         ent->solid = SOLID_TRIGGER;
  927.         ent->touch = Touch_Item;
  928.     }
  929.  
  930.     gi.linkentity (ent);
  931. }
  932.  
  933. //======================================================================
  934.  
  935. /*
  936. ================
  937. droptofloor
  938. ================
  939. */
  940. void droptofloor (edict_t *ent)
  941. {
  942.     trace_t        tr;
  943.     vec3_t        dest;
  944.     float        *v;
  945.  
  946.     v = tv(-15,-15,-15);
  947.     VectorCopy (v, ent->mins);
  948.     v = tv(15,15,15);
  949.     VectorCopy (v, ent->maxs);
  950.  
  951.     if (ent->model)
  952.         gi.setmodel (ent, ent->model);
  953.     else
  954.         gi.setmodel (ent, ent->item->world_model);
  955.     ent->solid = SOLID_TRIGGER;
  956.     ent->movetype = MOVETYPE_TOSS;  
  957.     ent->touch = Touch_Item;
  958.  
  959.     v = tv(0,0,-128);
  960.     VectorAdd (ent->s.origin, v, dest);
  961.  
  962.     tr = gi.trace (ent->s.origin, ent->mins, ent->maxs, dest, ent, MASK_SOLID);
  963.     if (tr.startsolid)
  964.     {
  965.         gi.dprintf ("droptofloor: %s startsolid at %s\n", ent->classname, vtos(ent->s.origin));
  966.         G_FreeEdict (ent);
  967.         return;
  968.     }
  969.  
  970.     VectorCopy (tr.endpos, ent->s.origin);
  971.  
  972.     if (ent->team)
  973.     {
  974.         ent->flags &= ~FL_TEAMSLAVE;
  975.         ent->chain = ent->teamchain;
  976.         ent->teamchain = NULL;
  977.  
  978.         ent->svflags |= SVF_NOCLIENT;
  979.         ent->solid = SOLID_NOT;
  980.         if (ent == ent->teammaster)
  981.         {
  982.             ent->nextthink = level.time + FRAMETIME;
  983.             ent->think = DoRespawn;
  984.         }
  985.     }
  986.  
  987.     if (ent->spawnflags & ITEM_NO_TOUCH)
  988.     {
  989.         ent->solid = SOLID_BBOX;
  990.         ent->touch = NULL;
  991.         ent->s.effects &= ~EF_ROTATE;
  992.         ent->s.renderfx &= ~RF_GLOW;
  993.     }
  994.  
  995.     if (ent->spawnflags & ITEM_TRIGGER_SPAWN)
  996.     {
  997.         ent->svflags |= SVF_NOCLIENT;
  998.         ent->solid = SOLID_NOT;
  999.         ent->use = Use_Item;
  1000.     }
  1001.  
  1002.     gi.linkentity (ent);
  1003. }
  1004.  
  1005.  
  1006. /*
  1007. ===============
  1008. PrecacheItem
  1009.  
  1010. Precaches all data needed for a given item.
  1011. This will be called for each item spawned in a level,
  1012. and for each item in each client's inventory.
  1013. ===============
  1014. */
  1015. void PrecacheItem (gitem_t *it)
  1016. {
  1017.     char    *s, *start;
  1018.     char    data[MAX_QPATH];
  1019.     int        len;
  1020.     gitem_t    *ammo;
  1021.  
  1022.     if (!it)
  1023.         return;
  1024.  
  1025.     if (it->pickup_sound)
  1026.         gi.soundindex (it->pickup_sound);
  1027.     if (it->world_model)
  1028.         gi.modelindex (it->world_model);
  1029.     if (it->view_model)
  1030.         gi.modelindex (it->view_model);
  1031.     if (it->icon)
  1032.         gi.imageindex (it->icon);
  1033.  
  1034.     // parse everything for its ammo
  1035.     if (it->ammo && it->ammo[0])
  1036.     {
  1037.         ammo = FindItem (it->ammo);
  1038.         if (ammo != it)
  1039.             PrecacheItem (ammo);
  1040.     }
  1041.  
  1042.     // parse the space seperated precache string for other items
  1043.     s = it->precaches;
  1044.     if (!s || !s[0])
  1045.         return;
  1046.  
  1047.     while (*s)
  1048.     {
  1049.         start = s;
  1050.         while (*s && *s != ' ')
  1051.             s++;
  1052.  
  1053.         len = s-start;
  1054.         if (len >= MAX_QPATH || len < 5)
  1055.             gi.error ("PrecacheItem: %s has bad precache string", it->classname);
  1056.         memcpy (data, start, len);
  1057.         data[len] = 0;
  1058.         if (*s)
  1059.             s++;
  1060.  
  1061.         // determine type based on extension
  1062.         if (!strcmp(data+len-3, "md2"))
  1063.             gi.modelindex (data);
  1064.         else if (!strcmp(data+len-3, "sp2"))
  1065.             gi.modelindex (data);
  1066.         else if (!strcmp(data+len-3, "wav"))
  1067.             gi.soundindex (data);
  1068.         if (!strcmp(data+len-3, "pcx"))
  1069.             gi.imageindex (data);
  1070.     }
  1071. }
  1072.  
  1073. /*
  1074. ============
  1075. SpawnItem
  1076.  
  1077. Sets the clipping size and plants the object on the floor.
  1078.  
  1079. Items can't be immediately dropped to floor, because they might
  1080. be on an entity that hasn't spawned yet.
  1081. ============
  1082. */
  1083. void SpawnItem (edict_t *ent, gitem_t *item)
  1084. {
  1085.     PrecacheItem (item);
  1086.  
  1087.     if (ent->spawnflags)
  1088.     {
  1089.         if (strcmp(ent->classname, "key_power_cube") != 0)
  1090.         {
  1091.             ent->spawnflags = 0;
  1092.             gi.dprintf("%s at %s has invalid spawnflags set\n", ent->classname, vtos(ent->s.origin));
  1093.         }
  1094.     }
  1095.  
  1096.     // some items will be prevented in deathmatch
  1097.     if (deathmatch->value)
  1098.     {
  1099.         if ( (int)dmflags->value & DF_NO_ARMOR )
  1100.         {
  1101.             if (item->pickup == Pickup_Armor || item->pickup == Pickup_PowerArmor)
  1102.             {
  1103.                 G_FreeEdict (ent);
  1104.                 return;
  1105.             }
  1106.         }
  1107.         if ( (int)dmflags->value & DF_NO_ITEMS )
  1108.         {
  1109.             if (item->pickup == Pickup_Powerup)
  1110.             {
  1111.                 G_FreeEdict (ent);
  1112.                 return;
  1113.             }
  1114.         }
  1115.         if ( (int)dmflags->value & DF_NO_HEALTH )
  1116.         {
  1117.             if (item->pickup == Pickup_Health || item->pickup == Pickup_Adrenaline || item->pickup == Pickup_AncientHead)
  1118.             {
  1119.                 G_FreeEdict (ent);
  1120.                 return;
  1121.             }
  1122.         }
  1123.         if ( (int)dmflags->value & DF_INFINITE_AMMO )
  1124.         {
  1125.             if ( (item->flags == IT_AMMO) || (strcmp(ent->classname, "weapon_bfg") == 0) )
  1126.             {
  1127.                 G_FreeEdict (ent);
  1128.                 return;
  1129.             }
  1130.         }
  1131.     }
  1132.  
  1133.     if (coop->value && (strcmp(ent->classname, "key_power_cube") == 0))
  1134.     {
  1135.         ent->spawnflags |= (1 << (8 + level.power_cubes));
  1136.         level.power_cubes++;
  1137.     }
  1138.  
  1139.     // don't let them drop items that stay in a coop game
  1140.     if ((coop->value) && (item->flags & IT_STAY_COOP))
  1141.     {
  1142.         item->drop = NULL;
  1143.     }
  1144.  
  1145. //ZOID
  1146. //Don't spawn the flags unless enabled
  1147.     if (!ctf->value &&
  1148.         (strcmp(ent->classname, "item_flag_team1") == 0 ||
  1149.         strcmp(ent->classname, "item_flag_team2") == 0)) {
  1150.         G_FreeEdict(ent);
  1151.         return;
  1152.     }
  1153. //ZOID
  1154.  
  1155.     ent->item = item;
  1156.     ent->nextthink = level.time + 2 * FRAMETIME;    // items start after other solids
  1157.     ent->think = droptofloor;
  1158.     ent->s.effects = item->world_model_flags;
  1159.     ent->s.renderfx = RF_GLOW;
  1160.     if (ent->model)
  1161.         gi.modelindex (ent->model);
  1162.  
  1163. //ZOID
  1164. //flags are server animated and have special handling
  1165.     if (strcmp(ent->classname, "item_flag_team1") == 0 ||
  1166.         strcmp(ent->classname, "item_flag_team2") == 0) {
  1167.         ent->think = CTFFlagSetup;
  1168.     }
  1169. //ZOID
  1170.  
  1171. }
  1172.  
  1173. //======================================================================
  1174.  
  1175. gitem_t    itemlist[] = 
  1176. {
  1177.     {
  1178.         NULL
  1179.     },    // leave index 0 alone
  1180.  
  1181.     //
  1182.     // ARMOR
  1183.     //
  1184.  
  1185. /*QUAKED item_armor_body (.3 .3 1) (-16 -16 -16) (16 16 16)
  1186. */
  1187.     {
  1188.         "item_armor_body", 
  1189.         Pickup_Armor,
  1190.         NULL,
  1191.         NULL,
  1192.         NULL,
  1193.         "misc/ar1_pkup.wav",
  1194.         "models/items/armor/body/tris.md2", EF_ROTATE,
  1195.         NULL,
  1196. /* icon */        "i_bodyarmor",
  1197. /* pickup */    "Body Armor",
  1198. /* width */        3,
  1199.         0,
  1200.         NULL,
  1201.         IT_ARMOR,
  1202.         0,
  1203.         &bodyarmor_info,
  1204.         ARMOR_BODY,
  1205. /* precache */ ""
  1206.     },
  1207.  
  1208. /*QUAKED item_armor_combat (.3 .3 1) (-16 -16 -16) (16 16 16)
  1209. */
  1210.     {
  1211.         "item_armor_combat", 
  1212.         Pickup_Armor,
  1213.         NULL,
  1214.         NULL,
  1215.         NULL,
  1216.         "misc/ar1_pkup.wav",
  1217.         "models/items/armor/combat/tris.md2", EF_ROTATE,
  1218.         NULL,
  1219. /* icon */        "i_combatarmor",
  1220. /* pickup */    "Combat Armor",
  1221. /* width */        3,
  1222.         0,
  1223.         NULL,
  1224.         IT_ARMOR,
  1225.         0,
  1226.         &combatarmor_info,
  1227.         ARMOR_COMBAT,
  1228. /* precache */ ""
  1229.     },
  1230.  
  1231. /*QUAKED item_armor_jacket (.3 .3 1) (-16 -16 -16) (16 16 16)
  1232. */
  1233.     {
  1234.         "item_armor_jacket", 
  1235.         Pickup_Armor,
  1236.         NULL,
  1237.         NULL,
  1238.         NULL,
  1239.         "misc/ar1_pkup.wav",
  1240.         "models/items/armor/jacket/tris.md2", EF_ROTATE,
  1241.         NULL,
  1242. /* icon */        "i_jacketarmor",
  1243. /* pickup */    "Jacket Armor",
  1244. /* width */        3,
  1245.         0,
  1246.         NULL,
  1247.         IT_ARMOR,
  1248.         0,
  1249.         &jacketarmor_info,
  1250.         ARMOR_JACKET,
  1251. /* precache */ ""
  1252.     },
  1253.  
  1254. /*QUAKED item_armor_shard (.3 .3 1) (-16 -16 -16) (16 16 16)
  1255. */
  1256.     {
  1257.         "item_armor_shard", 
  1258.         Pickup_Armor,
  1259.         NULL,
  1260.         NULL,
  1261.         NULL,
  1262.         "misc/ar2_pkup.wav",
  1263.         "models/items/armor/shard/tris.md2", EF_ROTATE,
  1264.         NULL,
  1265. /* icon */        "i_jacketarmor",
  1266. /* pickup */    "Armor Shard",
  1267. /* width */        3,
  1268.         0,
  1269.         NULL,
  1270.         IT_ARMOR,
  1271.         0,
  1272.         NULL,
  1273.         ARMOR_SHARD,
  1274. /* precache */ ""
  1275.     },
  1276.  
  1277.  
  1278. /*QUAKED item_power_screen (.3 .3 1) (-16 -16 -16) (16 16 16)
  1279. */
  1280.     {
  1281.         "item_power_screen", 
  1282.         Pickup_PowerArmor,
  1283.         Use_PowerArmor,
  1284.         Drop_PowerArmor,
  1285.         NULL,
  1286.         "misc/ar3_pkup.wav",
  1287.         "models/items/armor/screen/tris.md2", EF_ROTATE,
  1288.         NULL,
  1289. /* icon */        "i_powerscreen",
  1290. /* pickup */    "Power Screen",
  1291. /* width */        0,
  1292.         60,
  1293.         NULL,
  1294.         IT_ARMOR,
  1295.         0,
  1296.         NULL,
  1297.         0,
  1298. /* precache */ ""
  1299.     },
  1300.  
  1301. /*QUAKED item_power_shield (.3 .3 1) (-16 -16 -16) (16 16 16)
  1302. */
  1303.     {
  1304.         "item_power_shield",
  1305.         Pickup_PowerArmor,
  1306.         Use_PowerArmor,
  1307.         Drop_PowerArmor,
  1308.         NULL,
  1309.         "misc/ar3_pkup.wav",
  1310.         "models/items/armor/shield/tris.md2", EF_ROTATE,
  1311.         NULL,
  1312. /* icon */        "i_powershield",
  1313. /* pickup */    "Power Shield",
  1314. /* width */        0,
  1315.         60,
  1316.         NULL,
  1317.         IT_ARMOR,
  1318.         0,
  1319.         NULL,
  1320.         0,
  1321. /* precache */ "misc/power2.wav misc/power1.wav"
  1322.     },
  1323.  
  1324.  
  1325.     //
  1326.     // WEAPONS 
  1327.     //
  1328.  
  1329. /* weapon_grapple (.3 .3 1) (-16 -16 -16) (16 16 16)
  1330. always owned, never in the world
  1331. */
  1332.     {
  1333.         "weapon_grapple", 
  1334.         NULL,
  1335.         Use_Weapon,
  1336.         NULL,
  1337.         CTFWeapon_Grapple,
  1338.         "misc/w_pkup.wav",
  1339.         NULL, 0,
  1340.         "models/weapons/grapple/tris.md2",
  1341. /* icon */        "w_grapple",
  1342. /* pickup */    "Grapple",
  1343.         0,
  1344.         0,
  1345.         NULL,
  1346.         IT_WEAPON,
  1347.         WEAP_GRAPPLE,
  1348.         NULL,
  1349.         0,
  1350. /* precache */ "weapons/grapple/grfire.wav weapons/grapple/grpull.wav weapons/grapple/grhang.wav weapons/grapple/grreset.wav weapons/grapple/grhit.wav"
  1351.     },
  1352.  
  1353. /* weapon_blaster (.3 .3 1) (-16 -16 -16) (16 16 16)
  1354. always owned, never in the world
  1355. */
  1356.     {
  1357.         "weapon_blaster", 
  1358.         NULL,
  1359.         Use_Weapon,
  1360.         NULL,
  1361.         Weapon_Blaster,
  1362.         "misc/w_pkup.wav",
  1363.         NULL, 0,
  1364.         "models/weapons/v_blast/tris.md2",
  1365. /* icon */        "w_blaster",
  1366. /* pickup */    "Blaster",
  1367.         0,
  1368.         0,
  1369.         NULL,
  1370.         IT_WEAPON|IT_STAY_COOP,
  1371.         WEAP_BLASTER,
  1372.         NULL,
  1373.         0,
  1374. /* precache */ "weapons/blastf1a.wav misc/lasfly.wav"
  1375.     },
  1376.  
  1377.     
  1378. /*QUAKED weapon_shotgun (.3 .3 1) (-16 -16 -16) (16 16 16)
  1379. */
  1380.     {
  1381.         "weapon_shotgun", 
  1382.         Pickup_Weapon,
  1383.         Use_Weapon,
  1384.         Drop_Weapon,
  1385.         Weapon_Shotgun,
  1386.         "misc/w_pkup.wav",
  1387.         "models/weapons/g_shotg/tris.md2", EF_ROTATE,
  1388.         "models/weapons/v_shotg/tris.md2",
  1389. /* icon */        "w_shotgun",
  1390. /* pickup */    "Shotgun",
  1391.         0,
  1392.         1,
  1393.         "Shells",
  1394.         IT_WEAPON|IT_STAY_COOP,
  1395.         WEAP_SHOTGUN,
  1396.         NULL,
  1397.         0,
  1398. /* precache */ "weapons/shotgf1b.wav weapons/shotgr1b.wav"
  1399.     },
  1400.  
  1401. /*QUAKED weapon_supershotgun (.3 .3 1) (-16 -16 -16) (16 16 16)
  1402. */
  1403.     {
  1404.         "weapon_supershotgun", 
  1405.         Pickup_Weapon,
  1406.         Use_Weapon,
  1407.         Drop_Weapon,
  1408.         Weapon_SuperShotgun,
  1409.         "misc/w_pkup.wav",
  1410.         "models/weapons/g_shotg2/tris.md2", EF_ROTATE,
  1411.         "models/weapons/v_shotg2/tris.md2",
  1412. /* icon */        "w_sshotgun",
  1413. /* pickup */    "Super Shotgun",
  1414.         0,
  1415.         2,
  1416.         "Shells",
  1417.         IT_WEAPON|IT_STAY_COOP,
  1418.         WEAP_SUPERSHOTGUN,
  1419.         NULL,
  1420.         0,
  1421. /* precache */ "weapons/sshotf1b.wav"
  1422.     },
  1423.  
  1424. /*QUAKED weapon_machinegun (.3 .3 1) (-16 -16 -16) (16 16 16)
  1425. */
  1426.     {
  1427.         "weapon_machinegun", 
  1428.         Pickup_Weapon,
  1429.         Use_Weapon,
  1430.         Drop_Weapon,
  1431.         Weapon_Machinegun,
  1432.         "misc/w_pkup.wav",
  1433.         "models/weapons/g_machn/tris.md2", EF_ROTATE,
  1434.         "models/weapons/v_machn/tris.md2",
  1435. /* icon */        "w_machinegun",
  1436. /* pickup */    "Machinegun",
  1437.         0,
  1438.         1,
  1439.         "Bullets",
  1440.         IT_WEAPON|IT_STAY_COOP,
  1441.         WEAP_MACHINEGUN,
  1442.         NULL,
  1443.         0,
  1444. /* precache */ "weapons/machgf1b.wav weapons/machgf2b.wav weapons/machgf3b.wav weapons/machgf4b.wav weapons/machgf5b.wav"
  1445.     },
  1446.  
  1447. /*QUAKED weapon_chaingun (.3 .3 1) (-16 -16 -16) (16 16 16)
  1448. */
  1449.     {
  1450.         "weapon_chaingun", 
  1451.         Pickup_Weapon,
  1452.         Use_Weapon,
  1453.         Drop_Weapon,
  1454.         Weapon_Chaingun,
  1455.         "misc/w_pkup.wav",
  1456.         "models/weapons/g_chain/tris.md2", EF_ROTATE,
  1457.         "models/weapons/v_chain/tris.md2",
  1458. /* icon */        "w_chaingun",
  1459. /* pickup */    "Chaingun",
  1460.         0,
  1461.         1,
  1462.         "Bullets",
  1463.         IT_WEAPON|IT_STAY_COOP,
  1464.         WEAP_CHAINGUN,
  1465.         NULL,
  1466.         0,
  1467. /* precache */ "weapons/chngnu1a.wav weapons/chngnl1a.wav weapons/machgf3b.wav` weapons/chngnd1a.wav"
  1468.     },
  1469.  
  1470. /*QUAKED ammo_grenades (.3 .3 1) (-16 -16 -16) (16 16 16)
  1471. */
  1472.     {
  1473.         "ammo_grenades",
  1474.         Pickup_Ammo,
  1475.         Use_Weapon,
  1476.         Drop_Ammo,
  1477.         Weapon_Grenade,
  1478.         "misc/am_pkup.wav",
  1479.         "models/items/ammo/grenades/medium/tris.md2", 0,
  1480.         "models/weapons/v_handgr/tris.md2",
  1481. /* icon */        "a_grenades",
  1482. /* pickup */    "Grenades",
  1483. /* width */        3,
  1484.         5,
  1485.         "grenades",
  1486.         IT_AMMO|IT_WEAPON,
  1487.         WEAP_GRENADES,
  1488.         NULL,
  1489.         AMMO_GRENADES,
  1490. /* precache */ "weapons/hgrent1a.wav weapons/hgrena1b.wav weapons/hgrenc1b.wav weapons/hgrenb1a.wav weapons/hgrenb2a.wav "
  1491.     },
  1492.  
  1493. /*QUAKED weapon_grenadelauncher (.3 .3 1) (-16 -16 -16) (16 16 16)
  1494. */
  1495.     {
  1496.         "weapon_grenadelauncher",
  1497.         Pickup_Weapon,
  1498.         Use_Weapon,
  1499.         Drop_Weapon,
  1500.         Weapon_GrenadeLauncher,
  1501.         "misc/w_pkup.wav",
  1502.         "models/weapons/g_launch/tris.md2", EF_ROTATE,
  1503.         "models/weapons/v_launch/tris.md2",
  1504. /* icon */        "w_glauncher",
  1505. /* pickup */    "Grenade Launcher",
  1506.         0,
  1507.         1,
  1508.         "Grenades",
  1509.         IT_WEAPON|IT_STAY_COOP,
  1510.         WEAP_GRENADELAUNCHER,
  1511.         NULL,
  1512.         0,
  1513. /* precache */ "models/objects/grenade/tris.md2 weapons/grenlf1a.wav weapons/grenlr1b.wav weapons/grenlb1b.wav"
  1514.     },
  1515.  
  1516. /*QUAKED weapon_rocketlauncher (.3 .3 1) (-16 -16 -16) (16 16 16)
  1517. */
  1518.     {
  1519.         "weapon_rocketlauncher",
  1520.         Pickup_Weapon,
  1521.         Use_Weapon,
  1522.         Drop_Weapon,
  1523.         Weapon_RocketLauncher,
  1524.         "misc/w_pkup.wav",
  1525.         "models/weapons/g_rocket/tris.md2", EF_ROTATE,
  1526.         "models/weapons/v_rocket/tris.md2",
  1527. /* icon */        "w_rlauncher",
  1528. /* pickup */    "Rocket Launcher",
  1529.         0,
  1530.         1,
  1531.         "Rockets",
  1532.         IT_WEAPON|IT_STAY_COOP,
  1533.         WEAP_ROCKETLAUNCHER,
  1534.         NULL,
  1535.         0,
  1536. /* precache */ "models/objects/rocket/tris.md2 weapons/rockfly.wav weapons/rocklf1a.wav weapons/rocklr1b.wav models/objects/debris2/tris.md2"
  1537.     },
  1538.  
  1539. /*QUAKED weapon_hyperblaster (.3 .3 1) (-16 -16 -16) (16 16 16)
  1540. */
  1541.     {
  1542.         "weapon_hyperblaster", 
  1543.         Pickup_Weapon,
  1544.         Use_Weapon,
  1545.         Drop_Weapon,
  1546.         Weapon_HyperBlaster,
  1547.         "misc/w_pkup.wav",
  1548.         "models/weapons/g_hyperb/tris.md2", EF_ROTATE,
  1549.         "models/weapons/v_hyperb/tris.md2",
  1550. /* icon */        "w_hyperblaster",
  1551. /* pickup */    "HyperBlaster",
  1552.         0,
  1553.         1,
  1554.         "Cells",
  1555.         IT_WEAPON|IT_STAY_COOP,
  1556.         WEAP_HYPERBLASTER,
  1557.         NULL,
  1558.         0,
  1559. /* precache */ "weapons/hyprbu1a.wav weapons/hyprbl1a.wav weapons/hyprbf1a.wav weapons/hyprbd1a.wav misc/lasfly.wav"
  1560.     },
  1561.  
  1562. /*QUAKED weapon_railgun (.3 .3 1) (-16 -16 -16) (16 16 16)
  1563. */
  1564.     {
  1565.         "weapon_railgun", 
  1566.         Pickup_Weapon,
  1567.         Use_Weapon,
  1568.         Drop_Weapon,
  1569.         Weapon_Railgun,
  1570.         "misc/w_pkup.wav",
  1571.         "models/weapons/g_rail/tris.md2", EF_ROTATE,
  1572.         "models/weapons/v_rail/tris.md2",
  1573. /* icon */        "w_railgun",
  1574. /* pickup */    "Railgun",
  1575.         0,
  1576.         1,
  1577.         "Slugs",
  1578.         IT_WEAPON|IT_STAY_COOP,
  1579.         WEAP_RAILGUN,
  1580.         NULL,
  1581.         0,
  1582. /* precache */ "weapons/rg_hum.wav"
  1583.     },
  1584.  
  1585. /*QUAKED weapon_bfg (.3 .3 1) (-16 -16 -16) (16 16 16)
  1586. */
  1587.     {
  1588.         "weapon_bfg",
  1589.         Pickup_Weapon,
  1590.         Use_Weapon,
  1591.         Drop_Weapon,
  1592.         Weapon_BFG,
  1593.         "misc/w_pkup.wav",
  1594.         "models/weapons/g_bfg/tris.md2", EF_ROTATE,
  1595.         "models/weapons/v_bfg/tris.md2",
  1596. /* icon */        "w_bfg",
  1597. /* pickup */    "BFG10K",
  1598.         0,
  1599.         50,
  1600.         "Cells",
  1601.         IT_WEAPON|IT_STAY_COOP,
  1602.         WEAP_BFG,
  1603.         NULL,
  1604.         0,
  1605. /* precache */ "sprites/s_bfg1.sp2 sprites/s_bfg2.sp2 sprites/s_bfg3.sp2 weapons/bfg__f1y.wav weapons/bfg__l1a.wav weapons/bfg__x1b.wav weapons/bfg_hum.wav"
  1606.     },
  1607.  
  1608. #if 0
  1609. //ZOID
  1610. /*QUAKED weapon_laser (.3 .3 1) (-16 -16 -16) (16 16 16)
  1611. */
  1612.     {
  1613.         "weapon_laser",
  1614.         Pickup_Weapon,
  1615.         Use_Weapon,
  1616.         Drop_Weapon,
  1617.         Weapon_Laser,
  1618.         "misc/w_pkup.wav",
  1619.         "models/weapons/g_laser/tris.md2", EF_ROTATE,
  1620.         "models/weapons/v_laser/tris.md2",
  1621. /* icon */        "w_bfg",
  1622. /* pickup */    "Flashlight Laser",
  1623.         0,
  1624.         1,
  1625.         "Cells",
  1626.         IT_WEAPON,
  1627.         0,
  1628.         NULL,
  1629.         0,
  1630. /* precache */ ""
  1631.     },
  1632. #endif
  1633.  
  1634.     //
  1635.     // AMMO ITEMS
  1636.     //
  1637.  
  1638. /*QUAKED ammo_shells (.3 .3 1) (-16 -16 -16) (16 16 16)
  1639. */
  1640.     {
  1641.         "ammo_shells",
  1642.         Pickup_Ammo,
  1643.         NULL,
  1644.         Drop_Ammo,
  1645.         NULL,
  1646.         "misc/am_pkup.wav",
  1647.         "models/items/ammo/shells/medium/tris.md2", 0,
  1648.         NULL,
  1649. /* icon */        "a_shells",
  1650. /* pickup */    "Shells",
  1651. /* width */        3,
  1652.         10,
  1653.         NULL,
  1654.         IT_AMMO,
  1655.         0,
  1656.         NULL,
  1657.         AMMO_SHELLS,
  1658. /* precache */ ""
  1659.     },
  1660.  
  1661. /*QUAKED ammo_bullets (.3 .3 1) (-16 -16 -16) (16 16 16)
  1662. */
  1663.     {
  1664.         "ammo_bullets",
  1665.         Pickup_Ammo,
  1666.         NULL,
  1667.         Drop_Ammo,
  1668.         NULL,
  1669.         "misc/am_pkup.wav",
  1670.         "models/items/ammo/bullets/medium/tris.md2", 0,
  1671.         NULL,
  1672. /* icon */        "a_bullets",
  1673. /* pickup */    "Bullets",
  1674. /* width */        3,
  1675.         50,
  1676.         NULL,
  1677.         IT_AMMO,
  1678.         0,
  1679.         NULL,
  1680.         AMMO_BULLETS,
  1681. /* precache */ ""
  1682.     },
  1683.  
  1684. /*QUAKED ammo_cells (.3 .3 1) (-16 -16 -16) (16 16 16)
  1685. */
  1686.     {
  1687.         "ammo_cells",
  1688.         Pickup_Ammo,
  1689.         NULL,
  1690.         Drop_Ammo,
  1691.         NULL,
  1692.         "misc/am_pkup.wav",
  1693.         "models/items/ammo/cells/medium/tris.md2", 0,
  1694.         NULL,
  1695. /* icon */        "a_cells",
  1696. /* pickup */    "Cells",
  1697. /* width */        3,
  1698.         50,
  1699.         NULL,
  1700.         IT_AMMO,
  1701.         0,
  1702.         NULL,
  1703.         AMMO_CELLS,
  1704. /* precache */ ""
  1705.     },
  1706.  
  1707. /*QUAKED ammo_rockets (.3 .3 1) (-16 -16 -16) (16 16 16)
  1708. */
  1709.     {
  1710.         "ammo_rockets",
  1711.         Pickup_Ammo,
  1712.         NULL,
  1713.         Drop_Ammo,
  1714.         NULL,
  1715.         "misc/am_pkup.wav",
  1716.         "models/items/ammo/rockets/medium/tris.md2", 0,
  1717.         NULL,
  1718. /* icon */        "a_rockets",
  1719. /* pickup */    "Rockets",
  1720. /* width */        3,
  1721.         5,
  1722.         NULL,
  1723.         IT_AMMO,
  1724.         0,
  1725.         NULL,
  1726.         AMMO_ROCKETS,
  1727. /* precache */ ""
  1728.     },
  1729.  
  1730. /*QUAKED ammo_slugs (.3 .3 1) (-16 -16 -16) (16 16 16)
  1731. */
  1732.     {
  1733.         "ammo_slugs",
  1734.         Pickup_Ammo,
  1735.         NULL,
  1736.         Drop_Ammo,
  1737.         NULL,
  1738.         "misc/am_pkup.wav",
  1739.         "models/items/ammo/slugs/medium/tris.md2", 0,
  1740.         NULL,
  1741. /* icon */        "a_slugs",
  1742. /* pickup */    "Slugs",
  1743. /* width */        3,
  1744.         10,
  1745.         NULL,
  1746.         IT_AMMO,
  1747.         0,
  1748.         NULL,
  1749.         AMMO_SLUGS,
  1750. /* precache */ ""
  1751.     },
  1752.  
  1753.  
  1754.     //
  1755.     // POWERUP ITEMS
  1756.     //
  1757. /*QUAKED item_quad (.3 .3 1) (-16 -16 -16) (16 16 16)
  1758. */
  1759.     {
  1760.         "item_quad", 
  1761.         Pickup_Powerup,
  1762.         Use_Quad,
  1763.         Drop_General,
  1764.         NULL,
  1765.         "items/pkup.wav",
  1766.         "models/items/quaddama/tris.md2", EF_ROTATE,
  1767.         NULL,
  1768. /* icon */        "p_quad",
  1769. /* pickup */    "Quad Damage",
  1770. /* width */        2,
  1771.         60,
  1772.         NULL,
  1773.         IT_POWERUP,
  1774.         0,
  1775.         NULL,
  1776.         0,
  1777. /* precache */ "items/damage.wav items/damage2.wav items/damage3.wav"
  1778.     },
  1779.  
  1780. /*QUAKED item_invulnerability (.3 .3 1) (-16 -16 -16) (16 16 16)
  1781. */
  1782.     {
  1783.         "item_invulnerability",
  1784.         Pickup_Powerup,
  1785.         Use_Invulnerability,
  1786.         Drop_General,
  1787.         NULL,
  1788.         "items/pkup.wav",
  1789.         "models/items/invulner/tris.md2", EF_ROTATE,
  1790.         NULL,
  1791. /* icon */        "p_invulnerability",
  1792. /* pickup */    "Invulnerability",
  1793. /* width */        2,
  1794.         300,
  1795.         NULL,
  1796.         IT_POWERUP,
  1797.         0,
  1798.         NULL,
  1799.         0,
  1800. /* precache */ "items/protect.wav items/protect2.wav items/protect4.wav"
  1801.     },
  1802.  
  1803. /*QUAKED item_silencer (.3 .3 1) (-16 -16 -16) (16 16 16)
  1804. */
  1805.     {
  1806.         "item_silencer",
  1807.         Pickup_Powerup,
  1808.         Use_Silencer,
  1809.         Drop_General,
  1810.         NULL,
  1811.         "items/pkup.wav",
  1812.         "models/items/silencer/tris.md2", EF_ROTATE,
  1813.         NULL,
  1814. /* icon */        "p_silencer",
  1815. /* pickup */    "Silencer",
  1816. /* width */        2,
  1817.         60,
  1818.         NULL,
  1819.         IT_POWERUP,
  1820.         0,
  1821.         NULL,
  1822.         0,
  1823. /* precache */ ""
  1824.     },
  1825.  
  1826. /*QUAKED item_breather (.3 .3 1) (-16 -16 -16) (16 16 16)
  1827. */
  1828.     {
  1829.         "item_breather",
  1830.         Pickup_Powerup,
  1831.         Use_Breather,
  1832.         Drop_General,
  1833.         NULL,
  1834.         "items/pkup.wav",
  1835.         "models/items/breather/tris.md2", EF_ROTATE,
  1836.         NULL,
  1837. /* icon */        "p_rebreather",
  1838. /* pickup */    "Rebreather",
  1839. /* width */        2,
  1840.         60,
  1841.         NULL,
  1842.         IT_STAY_COOP|IT_POWERUP,
  1843.         0,
  1844.         NULL,
  1845.         0,
  1846. /* precache */ "items/airout.wav"
  1847.     },
  1848.  
  1849. /*QUAKED item_enviro (.3 .3 1) (-16 -16 -16) (16 16 16)
  1850. */
  1851.     {
  1852.         "item_enviro",
  1853.         Pickup_Powerup,
  1854.         Use_Envirosuit,
  1855.         Drop_General,
  1856.         NULL,
  1857.         "items/pkup.wav",
  1858.         "models/items/enviro/tris.md2", EF_ROTATE,
  1859.         NULL,
  1860. /* icon */        "p_envirosuit",
  1861. /* pickup */    "Environment Suit",
  1862. /* width */        2,
  1863.         60,
  1864.         NULL,
  1865.         IT_STAY_COOP|IT_POWERUP,
  1866.         0,
  1867.         NULL,
  1868.         0,
  1869. /* precache */ "items/airout.wav"
  1870.     },
  1871.  
  1872. /*QUAKED item_ancient_head (.3 .3 1) (-16 -16 -16) (16 16 16)
  1873. Special item that gives +2 to maximum health
  1874. */
  1875.     {
  1876.         "item_ancient_head",
  1877.         Pickup_AncientHead,
  1878.         NULL,
  1879.         NULL,
  1880.         NULL,
  1881.         "items/pkup.wav",
  1882.         "models/items/c_head/tris.md2", EF_ROTATE,
  1883.         NULL,
  1884. /* icon */        "i_fixme",
  1885. /* pickup */    "Ancient Head",
  1886. /* width */        2,
  1887.         60,
  1888.         NULL,
  1889.         0,
  1890.         0,
  1891.         NULL,
  1892.         0,
  1893. /* precache */ ""
  1894.     },
  1895.  
  1896. /*QUAKED item_adrenaline (.3 .3 1) (-16 -16 -16) (16 16 16)
  1897. gives +1 to maximum health
  1898. */
  1899.     {
  1900.         "item_adrenaline",
  1901.         Pickup_Adrenaline,
  1902.         NULL,
  1903.         NULL,
  1904.         NULL,
  1905.         "items/pkup.wav",
  1906.         "models/items/adrenal/tris.md2", EF_ROTATE,
  1907.         NULL,
  1908. /* icon */        "p_adrenaline",
  1909. /* pickup */    "Adrenaline",
  1910. /* width */        2,
  1911.         60,
  1912.         NULL,
  1913.         0,
  1914.         0,
  1915.         NULL,
  1916.         0,
  1917. /* precache */ ""
  1918.     },
  1919.  
  1920. /*QUAKED item_bandolier (.3 .3 1) (-16 -16 -16) (16 16 16)
  1921. */
  1922.     {
  1923.         "item_bandolier",
  1924.         Pickup_Bandolier,
  1925.         NULL,
  1926.         NULL,
  1927.         NULL,
  1928.         "items/pkup.wav",
  1929.         "models/items/band/tris.md2", EF_ROTATE,
  1930.         NULL,
  1931. /* icon */        "p_bandolier",
  1932. /* pickup */    "Bandolier",
  1933. /* width */        2,
  1934.         60,
  1935.         NULL,
  1936.         0,
  1937.         0,
  1938.         NULL,
  1939.         0,
  1940. /* precache */ ""
  1941.     },
  1942.  
  1943. /*QUAKED item_pack (.3 .3 1) (-16 -16 -16) (16 16 16)
  1944. */
  1945.     {
  1946.         "item_pack",
  1947.         Pickup_Pack,
  1948.         NULL,
  1949.         NULL,
  1950.         NULL,
  1951.         "items/pkup.wav",
  1952.         "models/items/pack/tris.md2", EF_ROTATE,
  1953.         NULL,
  1954. /* icon */        "i_pack",
  1955. /* pickup */    "Ammo Pack",
  1956. /* width */        2,
  1957.         180,
  1958.         NULL,
  1959.         0,
  1960.         0,
  1961.         NULL,
  1962.         0,
  1963. /* precache */ ""
  1964.     },
  1965.  
  1966.     //
  1967.     // KEYS
  1968.     //
  1969. /*QUAKED key_data_cd (0 .5 .8) (-16 -16 -16) (16 16 16)
  1970. key for computer centers
  1971. */
  1972.     {
  1973.         "key_data_cd",
  1974.         Pickup_Key,
  1975.         NULL,
  1976.         Drop_General,
  1977.         NULL,
  1978.         "items/pkup.wav",
  1979.         "models/items/keys/data_cd/tris.md2", EF_ROTATE,
  1980.         NULL,
  1981.         "k_datacd",
  1982.         "Data CD",
  1983.         2,
  1984.         0,
  1985.         NULL,
  1986.         IT_STAY_COOP|IT_KEY,
  1987.         0,
  1988.         NULL,
  1989.         0,
  1990. /* precache */ ""
  1991.     },
  1992.  
  1993. /*QUAKED key_power_cube (0 .5 .8) (-16 -16 -16) (16 16 16) TRIGGER_SPAWN NO_TOUCH
  1994. warehouse circuits
  1995. */
  1996.     {
  1997.         "key_power_cube",
  1998.         Pickup_Key,
  1999.         NULL,
  2000.         Drop_General,
  2001.         NULL,
  2002.         "items/pkup.wav",
  2003.         "models/items/keys/power/tris.md2", EF_ROTATE,
  2004.         NULL,
  2005.         "k_powercube",
  2006.         "Power Cube",
  2007.         2,
  2008.         0,
  2009.         NULL,
  2010.         IT_STAY_COOP|IT_KEY,
  2011.         0,
  2012.         NULL,
  2013.         0,
  2014. /* precache */ ""
  2015.     },
  2016.  
  2017. /*QUAKED key_pyramid (0 .5 .8) (-16 -16 -16) (16 16 16)
  2018. key for the entrance of jail3
  2019. */
  2020.     {
  2021.         "key_pyramid",
  2022.         Pickup_Key,
  2023.         NULL,
  2024.         Drop_General,
  2025.         NULL,
  2026.         "items/pkup.wav",
  2027.         "models/items/keys/pyramid/tris.md2", EF_ROTATE,
  2028.         NULL,
  2029.         "k_pyramid",
  2030.         "Pyramid Key",
  2031.         2,
  2032.         0,
  2033.         NULL,
  2034.         IT_STAY_COOP|IT_KEY,
  2035.         0,
  2036.         NULL,
  2037.         0,
  2038. /* precache */ ""
  2039.     },
  2040.  
  2041. /*QUAKED key_data_spinner (0 .5 .8) (-16 -16 -16) (16 16 16)
  2042. key for the city computer
  2043. */
  2044.     {
  2045.         "key_data_spinner",
  2046.         Pickup_Key,
  2047.         NULL,
  2048.         Drop_General,
  2049.         NULL,
  2050.         "items/pkup.wav",
  2051.         "models/items/keys/spinner/tris.md2", EF_ROTATE,
  2052.         NULL,
  2053.         "k_dataspin",
  2054.         "Data Spinner",
  2055.         2,
  2056.         0,
  2057.         NULL,
  2058.         IT_STAY_COOP|IT_KEY,
  2059.         0,
  2060.         NULL,
  2061.         0,
  2062. /* precache */ ""
  2063.     },
  2064.  
  2065. /*QUAKED key_pass (0 .5 .8) (-16 -16 -16) (16 16 16)
  2066. security pass for the security level
  2067. */
  2068.     {
  2069.         "key_pass",
  2070.         Pickup_Key,
  2071.         NULL,
  2072.         Drop_General,
  2073.         NULL,
  2074.         "items/pkup.wav",
  2075.         "models/items/keys/pass/tris.md2", EF_ROTATE,
  2076.         NULL,
  2077.         "k_security",
  2078.         "Security Pass",
  2079.         2,
  2080.         0,
  2081.         NULL,
  2082.         IT_STAY_COOP|IT_KEY,
  2083.         0,
  2084.         NULL,
  2085.         0,
  2086. /* precache */ ""
  2087.     },
  2088.  
  2089. /*QUAKED key_blue_key (0 .5 .8) (-16 -16 -16) (16 16 16)
  2090. normal door key - blue
  2091. */
  2092.     {
  2093.         "key_blue_key",
  2094.         Pickup_Key,
  2095.         NULL,
  2096.         Drop_General,
  2097.         NULL,
  2098.         "items/pkup.wav",
  2099.         "models/items/keys/key/tris.md2", EF_ROTATE,
  2100.         NULL,
  2101.         "k_bluekey",
  2102.         "Blue Key",
  2103.         2,
  2104.         0,
  2105.         NULL,
  2106.         IT_STAY_COOP|IT_KEY,
  2107.         0,
  2108.         NULL,
  2109.         0,
  2110. /* precache */ ""
  2111.     },
  2112.  
  2113. /*QUAKED key_red_key (0 .5 .8) (-16 -16 -16) (16 16 16)
  2114. normal door key - red
  2115. */
  2116.     {
  2117.         "key_red_key",
  2118.         Pickup_Key,
  2119.         NULL,
  2120.         Drop_General,
  2121.         NULL,
  2122.         "items/pkup.wav",
  2123.         "models/items/keys/red_key/tris.md2", EF_ROTATE,
  2124.         NULL,
  2125.         "k_redkey",
  2126.         "Red Key",
  2127.         2,
  2128.         0,
  2129.         NULL,
  2130.         IT_STAY_COOP|IT_KEY,
  2131.         0,
  2132.         NULL,
  2133.         0,
  2134. /* precache */ ""
  2135.     },
  2136.  
  2137. /*QUAKED key_commander_head (0 .5 .8) (-16 -16 -16) (16 16 16)
  2138. tank commander's head
  2139. */
  2140.     {
  2141.         "key_commander_head",
  2142.         Pickup_Key,
  2143.         NULL,
  2144.         Drop_General,
  2145.         NULL,
  2146.         "items/pkup.wav",
  2147.         "models/monsters/commandr/head/tris.md2", EF_GIB,
  2148.         NULL,
  2149. /* icon */        "k_comhead",
  2150. /* pickup */    "Commander's Head",
  2151. /* width */        2,
  2152.         0,
  2153.         NULL,
  2154.         IT_STAY_COOP|IT_KEY,
  2155.         0,
  2156.         NULL,
  2157.         0,
  2158. /* precache */ ""
  2159.     },
  2160.  
  2161. /*QUAKED key_airstrike_target (0 .5 .8) (-16 -16 -16) (16 16 16)
  2162. tank commander's head
  2163. */
  2164.     {
  2165.         "key_airstrike_target",
  2166.         Pickup_Key,
  2167.         NULL,
  2168.         Drop_General,
  2169.         NULL,
  2170.         "items/pkup.wav",
  2171.         "models/items/keys/target/tris.md2", EF_ROTATE,
  2172.         NULL,
  2173. /* icon */        "i_airstrike",
  2174. /* pickup */    "Airstrike Marker",
  2175. /* width */        2,
  2176.         0,
  2177.         NULL,
  2178.         IT_STAY_COOP|IT_KEY,
  2179.         0,
  2180.         NULL,
  2181.         0,
  2182. /* precache */ ""
  2183.     },
  2184.  
  2185.     {
  2186.         NULL,
  2187.         Pickup_Health,
  2188.         NULL,
  2189.         NULL,
  2190.         NULL,
  2191.         "items/pkup.wav",
  2192.         NULL, 0,
  2193.         NULL,
  2194. /* icon */        "i_health",
  2195. /* pickup */    "Health",
  2196. /* width */        3,
  2197.         0,
  2198.         NULL,
  2199.         0,
  2200.         0,
  2201.         NULL,
  2202.         0,
  2203. /* precache */ "items/s_health.wav items/n_health.wav items/l_health.wav items/m_health.wav"
  2204.     },
  2205.  
  2206.  
  2207. //ZOID
  2208. /*QUAKED item_flag_team1 (1 0.2 0) (-16 -16 -24) (16 16 32)
  2209. */
  2210.     {
  2211.         "item_flag_team1",
  2212.         CTFPickup_Flag,
  2213.         NULL,
  2214.         CTFDrop_Flag, //Should this be null if we don't want players to drop it manually?
  2215.         NULL,
  2216.         "ctf/flagtk.wav",
  2217.         "players/male/flag1.md2", EF_FLAG1,
  2218.         NULL,
  2219. /* icon */        "i_ctf1",
  2220. /* pickup */    "Red Flag",
  2221. /* width */        2,
  2222.         0,
  2223.         NULL,
  2224.         0,
  2225.         0,
  2226.         NULL,
  2227.         0,
  2228. /* precache */ "ctf/flagcap.wav"
  2229.     },
  2230.  
  2231. /*QUAKED item_flag_team2 (1 0.2 0) (-16 -16 -24) (16 16 32)
  2232. */
  2233.     {
  2234.         "item_flag_team2",
  2235.         CTFPickup_Flag,
  2236.         NULL,
  2237.         CTFDrop_Flag, //Should this be null if we don't want players to drop it manually?
  2238.         NULL,
  2239.         "ctf/flagtk.wav",
  2240.         "players/male/flag2.md2", EF_FLAG2,
  2241.         NULL,
  2242. /* icon */        "i_ctf2",
  2243. /* pickup */    "Blue Flag",
  2244. /* width */        2,
  2245.         0,
  2246.         NULL,
  2247.         0,
  2248.         0,
  2249.         NULL,
  2250.         0,
  2251. /* precache */ "ctf/flagcap.wav"
  2252.     },
  2253.  
  2254. /* Resistance Tech */
  2255.     {
  2256.         "item_tech1",
  2257.         CTFPickup_Tech,
  2258.         NULL,
  2259.         CTFDrop_Tech, //Should this be null if we don't want players to drop it manually?
  2260.         NULL,
  2261.         "items/pkup.wav",
  2262.         "models/ctf/resistance/tris.md2", EF_ROTATE,
  2263.         NULL,
  2264. /* icon */        "tech1",
  2265. /* pickup */    "Disruptor Shield",
  2266. /* width */        2,
  2267.         0,
  2268.         NULL,
  2269.         IT_TECH,
  2270.         0,
  2271.         NULL,
  2272.         0,
  2273. /* precache */ "ctf/tech1.wav"
  2274.     },
  2275.  
  2276. /* Strength Tech */
  2277.     {
  2278.         "item_tech2",
  2279.         CTFPickup_Tech,
  2280.         NULL,
  2281.         CTFDrop_Tech, //Should this be null if we don't want players to drop it manually?
  2282.         NULL,
  2283.         "items/pkup.wav",
  2284.         "models/ctf/strength/tris.md2", EF_ROTATE,
  2285.         NULL,
  2286. /* icon */        "tech2",
  2287. /* pickup */    "Power Amplifier",
  2288. /* width */        2,
  2289.         0,
  2290.         NULL,
  2291.         IT_TECH,
  2292.         0,
  2293.         NULL,
  2294.         0,
  2295. /* precache */ "ctf/tech2.wav ctf/tech2x.wav"
  2296.     },
  2297.  
  2298. /* Haste Tech */
  2299.     {
  2300.         "item_tech3",
  2301.         CTFPickup_Tech,
  2302.         NULL,
  2303.         CTFDrop_Tech, //Should this be null if we don't want players to drop it manually?
  2304.         NULL,
  2305.         "items/pkup.wav",
  2306.         "models/ctf/haste/tris.md2", EF_ROTATE,
  2307.         NULL,
  2308. /* icon */        "tech3",
  2309. /* pickup */    "Time Accel",
  2310. /* width */        2,
  2311.         0,
  2312.         NULL,
  2313.         IT_TECH,
  2314.         0,
  2315.         NULL,
  2316.         0,
  2317. /* precache */ "ctf/tech3.wav"
  2318.     },
  2319.  
  2320. /* Regeneration Tech */
  2321.     {
  2322.         "item_tech4",
  2323.         CTFPickup_Tech,
  2324.         NULL,
  2325.         CTFDrop_Tech, //Should this be null if we don't want players to drop it manually?
  2326.         NULL,
  2327.         "items/pkup.wav",
  2328.         "models/ctf/regeneration/tris.md2", EF_ROTATE,
  2329.         NULL,
  2330. /* icon */        "tech4",
  2331. /* pickup */    "AutoDoc",
  2332. /* width */        2,
  2333.         0,
  2334.         NULL,
  2335.         IT_TECH,
  2336.         0,
  2337.         NULL,
  2338.         0,
  2339. /* precache */ "ctf/tech4.wav"
  2340.     },
  2341.  
  2342. //ZOID
  2343.  
  2344.     // end of list marker
  2345.     {NULL}
  2346. };
  2347.  
  2348.  
  2349. /*QUAKED item_health (.3 .3 1) (-16 -16 -16) (16 16 16)
  2350. */
  2351. void SP_item_health (edict_t *self)
  2352. {
  2353.     if ( deathmatch->value && ((int)dmflags->value & DF_NO_HEALTH) )
  2354.     {
  2355.         G_FreeEdict (self);
  2356.         return;
  2357.     }
  2358.  
  2359.     self->model = "models/items/healing/medium/tris.md2";
  2360.     self->count = 10;
  2361.     SpawnItem (self, FindItem ("Health"));
  2362.     gi.soundindex ("items/n_health.wav");
  2363. }
  2364.  
  2365. /*QUAKED item_health_small (.3 .3 1) (-16 -16 -16) (16 16 16)
  2366. */
  2367. void SP_item_health_small (edict_t *self)
  2368. {
  2369.     if ( deathmatch->value && ((int)dmflags->value & DF_NO_HEALTH) )
  2370.     {
  2371.         G_FreeEdict (self);
  2372.         return;
  2373.     }
  2374.  
  2375.     self->model = "models/items/healing/stimpack/tris.md2";
  2376.     self->count = 2;
  2377.     SpawnItem (self, FindItem ("Health"));
  2378.     self->style = HEALTH_IGNORE_MAX;
  2379.     gi.soundindex ("items/s_health.wav");
  2380. }
  2381.  
  2382. /*QUAKED item_health_large (.3 .3 1) (-16 -16 -16) (16 16 16)
  2383. */
  2384. void SP_item_health_large (edict_t *self)
  2385. {
  2386.     if ( deathmatch->value && ((int)dmflags->value & DF_NO_HEALTH) )
  2387.     {
  2388.         G_FreeEdict (self);
  2389.         return;
  2390.     }
  2391.  
  2392.     self->model = "models/items/healing/large/tris.md2";
  2393.     self->count = 25;
  2394.     SpawnItem (self, FindItem ("Health"));
  2395.     gi.soundindex ("items/l_health.wav");
  2396. }
  2397.  
  2398. /*QUAKED item_health_mega (.3 .3 1) (-16 -16 -16) (16 16 16)
  2399. */
  2400. void SP_item_health_mega (edict_t *self)
  2401. {
  2402.     if ( deathmatch->value && ((int)dmflags->value & DF_NO_HEALTH) )
  2403.     {
  2404.         G_FreeEdict (self);
  2405.         return;
  2406.     }
  2407.  
  2408.     self->model = "models/items/mega_h/tris.md2";
  2409.     self->count = 100;
  2410.     SpawnItem (self, FindItem ("Health"));
  2411.     gi.soundindex ("items/m_health.wav");
  2412.     self->style = HEALTH_IGNORE_MAX|HEALTH_TIMED;
  2413. }
  2414.  
  2415.  
  2416. void InitItems (void)
  2417. {
  2418.     game.num_items = sizeof(itemlist)/sizeof(itemlist[0]) - 1;
  2419. }
  2420.  
  2421.  
  2422.  
  2423. /*
  2424. ===============
  2425. SetItemNames
  2426.  
  2427. Called by worldspawn
  2428. ===============
  2429. */
  2430. void SetItemNames (void)
  2431. {
  2432.     int        i;
  2433.     gitem_t    *it;
  2434.  
  2435.     for (i=0 ; i<game.num_items ; i++)
  2436.     {
  2437.         it = &itemlist[i];
  2438.         gi.configstring (CS_ITEMS+i, it->pickup_name);
  2439.     }
  2440.  
  2441.     jacket_armor_index = ITEM_INDEX(FindItem("Jacket Armor"));
  2442.     combat_armor_index = ITEM_INDEX(FindItem("Combat Armor"));
  2443.     body_armor_index   = ITEM_INDEX(FindItem("Body Armor"));
  2444.     power_screen_index = ITEM_INDEX(FindItem("Power Screen"));
  2445.     power_shield_index = ITEM_INDEX(FindItem("Power Shield"));
  2446. }
  2447.